﻿using System;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;

namespace Main.src.display
{

    /// <summary>
    /// Plano no qual a textura se reflete na horizontal e vertical
    /// </summary>
    public sealed class Plane : DisplayObject
    {

        public Texture2D Texture = null; // Textura

        /// <summary>
        /// Construtor
        /// </summary>
        /// <param name="texture">Textura</param>
        public Plane(Texture2D texture)
        {
            Texture = texture;
        }

        /// <summary>
        /// Desenha na tela
        /// </summary>
        /// <param name="spriteBatch">SpriteBatch do Main</param>
        public override void Draw(SpriteBatch spriteBatch)
        {
            if (Texture == null)
                return;

            float width, height;

            if (SourceRectangle.HasValue)
            {
                width  = SourceRectangle.Value.Width;
                height = SourceRectangle.Value.Height;
            }
            else
            {
                width  = Texture.Width;
                height = Texture.Height;
            }

            width  = width  * Scale.X;
            height = height * Scale.Y;

            float realOX = Origin.X % width;
            if (realOX < 0)
                realOX += width;

            float realOY = Origin.Y % height;
            if (realOY < 0)
                realOY += height;

            int angle = (int)Degrees % 360;
            if (angle < 0)
                angle += 360;

            Vector2 position = Vector2.Zero;

            if (angle == 0)
            {
                int maxX = (int)Math.Max(Math.Ceiling((float)Display.Width / width), 1) + 1;
                int maxY = (int)Math.Max(Math.Ceiling((float)Display.Height / height), 1) + 1;

                Vector2 origin = Vector2.Zero;

                for (int y = 0; y < maxY; y++)
                    for (int x = 0; x < maxX; x++)
                    {
                        origin.X = realOX + (x - maxX + 1) * width;
                        origin.Y = realOY + (y - maxY + 1) * height;
                        spriteBatch.Draw(Texture, position, SourceRectangle, Color, Rotation, origin, Scale, Effects, LayerDepth);
                    }
            }
            else
            {
                double cos = Math.Cos(Rotation);
                double sin = Math.Sin(Rotation);

                int maxX = (int)(Math.Max(Math.Ceiling((Math.Abs(Display.Width * cos) + Math.Abs(Display.Height * sin)) / width), 1)) + 1;
                int maxY = (int)(Math.Max(Math.Ceiling((Math.Abs(Display.Height * cos) + Math.Abs(Display.Width * sin)) / height), 1)) + 1;

                Vector2 pOrigin;

                if (angle <= 90)
                    pOrigin = new Vector2((float)(Display.Width * sin * sin), -(float)(Display.Width * Math.Abs(sin * cos)));
                else if (angle <= 180)
                    pOrigin = new Vector2(Display.Width + (float)(Display.Height * Math.Abs(sin * cos)), (float)(Display.Height * cos * cos));
                else if (angle <= 270)
                    pOrigin = new Vector2((float)(Display.Width * cos * cos), Display.Height + (float)(Display.Width * Math.Abs(cos * sin)));
                else
                    pOrigin = new Vector2(-(float)(Display.Height * Math.Abs(cos * sin)), (float)(Display.Height * sin * sin));

                Vector2 origin = new Vector2(realOX, realOY);
                
                for (int y = 0; y < maxY; y++)
                    for (int x = 0; x < maxX; x++)
                    {
                        float rx = x * width;
                        float ry = y * height;
                        position.X = (float)(rx * cos - ry * sin);
                        position.Y = (float)(rx * sin + ry * cos);
                        spriteBatch.Draw(Texture, pOrigin + position, SourceRectangle, Color, Rotation, origin, Scale, Effects, LayerDepth);
                    }
            }
        }

        /// <summary>
        /// Destrutor
        /// </summary>
        public override void Dispose()
        {
            base.Dispose();
            Texture = null;
        }

    }

}